package com.clkj.aimin.pojo.common;

import com.alibaba.fastjson.JSONObject;
import com.google.zxing.BarcodeFormat;
import com.google.zxing.EncodeHintType;
import com.google.zxing.MultiFormatWriter;
import com.google.zxing.common.BitMatrix;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.HttpEntity;
import org.apache.http.ParseException;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicHeader;
import org.apache.http.protocol.HTTP;
import org.apache.http.ssl.SSLContexts;
import org.apache.http.util.EntityUtils;
import org.springframework.mock.web.MockMultipartFile;
import org.springframework.web.multipart.MultipartFile;

import javax.imageio.ImageIO;
import javax.net.ssl.SSLContext;
import javax.servlet.http.HttpServletRequest;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.security.KeyStore;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.util.*;

public class Util {

    public static JSONObject getResult(String url) {
        JSONObject demoJson = null;
        try {
            URL urlGet = new URL(url);
            HttpURLConnection http = (HttpURLConnection) urlGet.openConnection();
            http.setRequestMethod("GET");

            http.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");

            http.setDoOutput(true);

            http.setDoInput(true);

            System.setProperty("sun.net.client.defaultConnectTimeout", "30000");

            System.setProperty("sun.net.client.defaultReadTimeout", "30000");

            http.connect();


            InputStream is = http.getInputStream();

            int size = is.available();
            byte[] jsonBytes = new byte[size];

            is.read(jsonBytes);
            String message = new String(jsonBytes, "UTF-8");
            System.out.println(message);
            new JSONObject();
            demoJson = JSONObject.parseObject(message);


            is.close();

            http.disconnect();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return demoJson;
    }

    public static String byteToHex(byte[] hash) {
        Formatter formatter = new Formatter();
        byte[] arrayOfByte = hash;
        int j = hash.length;
        for (int i = 0; i < j; i++) {
            byte b = arrayOfByte[i];
            formatter.format("%02x", new Object[]{Byte.valueOf(b)});
        }
        String result = formatter.toString();
        formatter.close();
        return result;
    }


    public static String getSignature(String jsapi_ticket, String timestamp, String nonce, String jsurl)
            throws IOException {
        String[] paramArr = {"jsapi_ticket=" + jsapi_ticket,
                "timestamp=" + timestamp, "noncestr=" + nonce, "url=" + jsurl};
        Arrays.sort(paramArr);

        String content = paramArr[0].concat("&" + paramArr[1]).concat("&" + paramArr[2])
                .concat("&" + paramArr[3]);
        String gensignature = null;
        try {
            MessageDigest md = MessageDigest.getInstance("SHA-1");

            byte[] digest = md.digest(content.toString().getBytes());
            gensignature = byteToStr(digest);
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
        if (gensignature != null) {
            return gensignature;
        }
        return "false";
    }


    private static String byteToStr(byte[] byteArray) {
        String strDigest = "";
        for (int i = 0; i < byteArray.length; i++) {
            strDigest = strDigest + byteToHexStr(byteArray[i]);
        }
        return strDigest;
    }

    private static String byteToHexStr(byte mByte) {
        char[] Digit = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A',
                'B', 'C', 'D', 'E', 'F'};
        char[] tempArr = new char[2];
        tempArr[0] = Digit[(mByte >>> 4 & 0xF)];
        tempArr[1] = Digit[(mByte & 0xF)];
        String s = new String(tempArr);
        return s;
    }

    /**
     * StringUtils工具类方法
     * 获取一定长度的随机字符串，范围0-9，a-z
     *
     * @param length：指定字符串长度
     * @return 一定长度的随机字符串
     */
    public static String getRandomStringByLength(int length) {
        String base = "abcdefghijklmnopqrstuvwxyz0123456789";
        Random random = new Random();
        StringBuffer sb = new StringBuffer();
        for (int i = 0; i < length; i++) {
            int number = random.nextInt(base.length());
            sb.append(base.charAt(number));
        }
        return sb.toString();
    }

    /**
     * 金额转换
     *
     * @param amount 具体金额
     * @return
     */
    public static String getMoney(String amount) {
        if (amount == null) {
            return "";
        }
        String currency = amount.replaceAll("\\$|\\￥|\\,", "");
        int index = currency.indexOf(".");
        int length = currency.length();
        Long amLong = Long.valueOf(0L);
        if (index == -1) {
            amLong = Long.valueOf(currency + "00");
        } else if (length - index >= 3) {
            amLong = Long.valueOf(currency.substring(0, index + 3).replace(".",
                    ""));
        } else if (length - index == 2) {
            amLong = Long.valueOf(currency.substring(0, index + 2).replace(".",
                    "") + 0);
        } else {
            amLong = Long.valueOf(currency.substring(0, index + 1).replace(".",
                    "")
                    + "00");
        }
        return amLong.toString();
    }

    /***　　sendUrl    （远程请求的URL）
     * 　　param    （远程请求参数）*
     * 　　JSONObject    （远程请求返回的JSON）
     *
     * */
    public static JSONObject sendPostUrl(String url, String param) {
        PrintWriter out = null;
        BufferedReader in = null;
        JSONObject jsonObject = null;
        String result = "";
        try {
            URL realUrl = new URL(url);
            // 打开和URL之间的连接
            URLConnection conn = realUrl.openConnection();
            // 发送POST请求必须设置如下两行
            conn.setDoOutput(true);
            conn.setDoInput(true);
            // 获取URLConnection对象对应的输出流（设置请求编码为UTF-8）
            out = new PrintWriter(new OutputStreamWriter(conn.getOutputStream(), "UTF-8"));
            // 发送请求参数
            out.print(param);
            // flush输出流的缓冲
            out.flush();
            // 获取请求返回数据（设置返回数据编码为UTF-8）
            in = new BufferedReader(
                    new InputStreamReader(conn.getInputStream(), "UTF-8"));
            String line;
            while ((line = in.readLine()) != null) {
                result += line;
            }
            jsonObject = JSONObject.parseObject(result);
            System.out.println(jsonObject);
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                if (out != null) {
                    out.close();
                }
                if (in != null) {
                    in.close();
                }
            } catch (IOException ex) {
                ex.printStackTrace();
            }
        }

        return jsonObject;
    }

    /**
     * 发送post请求
     *
     * @param url        路径
     * @param jsonObject 参数(json类型)
     * @param encoding   编码格式
     * @return
     * @throws ParseException
     * @throws IOException
     */
    public static String send(String url, JSONObject jsonObject, String encoding) throws ParseException, IOException {
        String body = "";

        //创建httpclient对象
        CloseableHttpClient client = HttpClients.createDefault();
        //创建post方式请求对象
        HttpPost httpPost = new HttpPost(url);

        //装填参数
        StringEntity s = new StringEntity(jsonObject.toString(), "utf-8");
        s.setContentEncoding(new BasicHeader(HTTP.CONTENT_TYPE,
                "application/json"));
        //设置参数到请求对象中
        httpPost.setEntity(s);
        System.out.println("请求地址：" + url);
//        System.out.println("请求参数："+nvps.toString());

        //设置header信息
        //指定报文头【Content-type】、【User-Agent】
//        httpPost.setHeader("Content-type", "application/x-www-form-urlencoded");
        httpPost.setHeader("Content-type", "application/json");
        httpPost.setHeader("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");

        //执行请求操作，并拿到结果（同步阻塞）
        CloseableHttpResponse response = client.execute(httpPost);
        //获取结果实体
        HttpEntity entity = response.getEntity();
        if (entity != null) {
            //按指定编码转换结果实体为String类型
            body = EntityUtils.toString(entity, encoding);
        }
        EntityUtils.consume(entity);
        //释放链接
        response.close();
        return body;
    }

    /**
     * IpUtils工具类方法 获取真实的ip地址
     *
     * @param request
     * @return
     */
    public static String getIpAddr(HttpServletRequest request) {
        try {
            String ip = request.getHeader("X-Forwarded-For");
            if (StringUtils.isNotEmpty(ip) && !"unKnown".equalsIgnoreCase(ip)) {
                // 多次反向代理后会有多个ip值，第一个ip才是真实ip
                int index = ip.indexOf(",");
                if (index != -1) {
                    return ip.substring(0, index);
                } else {
                    return ip;
                }
            }
            ip = request.getHeader("X-Real-IP");
            if (StringUtils.isNotEmpty(ip) && !"unKnown".equalsIgnoreCase(ip)) {
                return ip;
            }
            return request.getRemoteAddr();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    public static String createSHA1Sign(SortedMap<String, String> signParams)
            throws Exception {
        StringBuffer sb = new StringBuffer();
        Set es = signParams.entrySet();
        Iterator it = es.iterator();
        while (it.hasNext()) {
            Map.Entry entry = (Map.Entry) it.next();
            String k = (String) entry.getKey();
            String v = (String) entry.getValue();
            sb.append(k + "=" + v + "&");
        }
        String params = sb.substring(0, sb.lastIndexOf("&"));

        return getSha1(params);
    }

    public static String getSha1(String str) {
        if ((str == null) || (str.length() == 0)) {
            return null;
        }
        char[] hexDigits = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
                'a', 'b', 'c', 'd', 'e', 'f'};
        try {
            MessageDigest mdTemp = MessageDigest.getInstance("SHA1");
            mdTemp.update(str.getBytes("GBK"));

            byte[] md = mdTemp.digest();
            int j = md.length;
            char[] buf = new char[j * 2];
            int k = 0;
            for (int i = 0; i < j; i++) {
                byte byte0 = md[i];
                buf[(k++)] = hexDigits[(byte0 >>> 4 & 0xF)];
                buf[(k++)] = hexDigits[(byte0 & 0xF)];
            }
            return new String(buf);
        } catch (Exception e) {
        }
        return null;
    }

    /**
     * 发起退款
     *
     * @param url
     * @param data
     * @param mch_id
     * @return
     * @throws Exception
     */
    public static String doRefund(String url, String data, String mch_id)
            throws Exception {
        KeyStore keyStore = KeyStore.getInstance("PKCS12");
        String urlP = "D:/app_cert/shopping/" + mch_id + "/apiclient_cert.p12";
        FileInputStream instream = new FileInputStream(new File(urlP));// P12文件在服务器磁盘中的目录
        try {
            keyStore.load(instream, mch_id.toCharArray());// 这里写密码..默认是你的MCHID
        } finally {
            instream.close();
        }
        SSLContext sslcontext = SSLContexts.custom()
                .loadKeyMaterial(keyStore, mch_id.toCharArray())// 这里也是写密码的
                .build();
        SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(
                sslcontext, new String[]{"TLSv1"}, null,
                SSLConnectionSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
        CloseableHttpClient httpclient = HttpClients.custom()
                .setSSLSocketFactory(sslsf).build();
        try {
            HttpPost httpost = new HttpPost(url); // 设置响应头信息
            httpost.addHeader("Connection", "keep-alive");
            httpost.addHeader("Accept", "*/*");
            httpost.addHeader("Content-Type",
                    "application/x-www-form-urlencoded; charset=UTF-8");
            httpost.addHeader("Host", "api.mch.weixin.qq.com");
            httpost.addHeader("X-Requested-With", "XMLHttpRequest");
            httpost.addHeader("Cache-Control", "max-age=0");
            httpost.addHeader("User-Agent",
                    "Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.0) ");
            httpost.setEntity(new StringEntity(data, "UTF-8"));
            CloseableHttpResponse response = httpclient.execute(httpost);
            try {
                HttpEntity entity = response.getEntity();

                String jsonStr = EntityUtils.toString(response.getEntity(),
                        "UTF-8");
                EntityUtils.consume(entity);
                return jsonStr;
            } finally {
                response.close();
            }
        } finally {
            httpclient.close();
        }
    }

    public static String getGUID() {
        StringBuilder uid = new StringBuilder();
        //产生16位的强随机数
        Random rd = new SecureRandom();
        for (int i = 0; i < 16; i++) {
            //产生0-2的3位随机数
            int type = rd.nextInt(3);
            switch (type){
                case 0:
                    //0-9的随机数
                    uid.append(rd.nextInt(10));
                    break;
                case 1:
                    //ASCII在65-90之间为大写,获取大写随机
                    uid.append((char)(rd.nextInt(25)+65));
                    break;
                case 2:
                    //ASCII在97-122之间为小写，获取小写随机
                    uid.append((char)(rd.nextInt(25)+97));
                    break;
                default:
                    break;
            }
        }
        return uid.toString();
    }

    /**
     * StringUtils工具类方法
     * 获取一定长度的随机字符串，范围0-9
     *
     * @param length：指定字符串长度
     * @return 一定长度的随机字符串
     */
    public static String getRandomIntegerByLength(int length) {
        String base = "0123456789";
        Random random = new Random();
        StringBuffer sb = new StringBuffer();
        for (int i = 0; i < length; i++) {
            int number = random.nextInt(base.length());
            sb.append(base.charAt(number));
        }
        return sb.toString();
    }

        public static String creatPic(String url, String id, String path,String shopName) {
        try {
            String text = url;
            int width = 300;
            int height = 300;
            String format = "png";
            Hashtable<EncodeHintType, String> hints = new Hashtable<EncodeHintType, String>();
            hints.put(EncodeHintType.CHARACTER_SET, "utf-8");
            BitMatrix bitMatrix = new MultiFormatWriter().encode(text,
                    BarcodeFormat.QR_CODE, width, height, hints);
            File outputFile = new File(path + File.separator + id + ".png");
            QRUtil.writeToFile(bitMatrix, format, outputFile);
//            String picName = pressText(shopName, outputFile);
//            System.out.println(shopName);


        } catch (Exception e) {
            e.printStackTrace();
        }
            return null;
    }

    public static String pressText(String text, File ewm) {
        try {
//            text = new String(text.getBytes(),"utf-8");
            Image src   = ImageIO.read(ewm);
            int imageW= 400;//src.getWidth(null);
            int imageH =400;//src.getWidth(null);
            System.out.println(text);
            BufferedImage image = new BufferedImage(imageW,imageH,BufferedImage.TYPE_INT_BGR);
            Graphics g= image.createGraphics();
            g.drawImage(src,0,0,imageW,imageH,null);
            g.setColor(Color.black);
            Font font = new Font("宋体",Font.BOLD,18);
            FontMetrics metrics = g.getFontMetrics(font);
            //文字在图片中的坐标 这里设置在中间
            int startX = (imageW - metrics.stringWidth(text)) / 2;
            int startY = 380;
            g.setFont(font);
            g.drawString(text, startX, startY);
            g.dispose();
            FileOutputStream out = new FileOutputStream(ewm);
            ImageIO.write(image, "JPEG", out);
            out.close();
            System.out.println("image press success");
            MultipartFile cMultiFile = new MockMultipartFile("outputFile", ewm.getName(), null, new FileInputStream(ewm));
            String picName = OSSUtil.uploadingImg(cMultiFile,"er");
            return picName;

        } catch (Exception e) {
            e.printStackTrace();
        }
        return "";
    }

    /**
     * 将二进制转换成文件保存
     *
     * @param instreams 二进制流
     * @param imgPath   图片的保存路径
     * @param imgName   图片的名称
     * @return 1：保存正常
     * 0：保存失败
     */
    public static int saveToImgByInputStream(InputStream instreams, String imgPath, String imgName) {
        int stateInt = 1;
        if (instreams != null) {
            try {
                File file = new File(imgPath, imgName);//可以是任何图片格式.jpg,.png等
                File filePath = new File(imgPath);
                if (filePath.exists()) {
                    if (filePath.isDirectory()) {
                        System.out.println("dir exists");
                    } else {
                        System.out.println("the same name file exists, can not create dir");
                    }
                } else {
                    System.out.println("dir not exists, create it ...");
                    filePath.mkdir();
                }
                FileOutputStream fos = new FileOutputStream(file);
                byte[] b = new byte[1024];
                int nRead = 0;
                while ((nRead = instreams.read(b)) != -1) {
                    fos.write(b, 0, nRead);
                }
                MultipartFile cMultiFile = new MockMultipartFile("outputFile", file.getName(), null, new FileInputStream(file));
                OSSUtil.nameUploadingImg(cMultiFile,"erweima",imgName);
                fos.flush();
                fos.close();
            } catch (Exception e) {
                stateInt = 0;
                e.printStackTrace();
            } finally {
            }
        }
        return stateInt;//1 成功，0 失败
    }


}
